﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Diagnostics;
using System.Collections;

namespace Tool
{	
	static public class Container
	{
		public static void CopyList<K>( List<K> oSrc, ref List<K> oDst )
		{						
			if( typeof(K).IsPrimitive )
			{
				oSrc.AddRange(oSrc);
			}
			else if( typeof(K) is ICloneable)
			{
				foreach( K Key in oSrc )
				{
					oDst.Add( (K)((ICloneable)Key).Clone() );
				}
			}
		}

		public static Dictionary<K,V> GetCloneDico<K,V>( Dictionary<K,V> oDicoSrc )
		{						
			Dictionary<K,V> oDicoDst = new Dictionary<K,V>();

			if( typeof(K).IsPrimitive )
			{
				foreach( KeyValuePair<K, V> oEntry in oDicoSrc )
				{					
					oDicoDst.Add( oEntry.Key, (V)((ICloneable)oEntry.Value).Clone() );
				}
			}
			else if( typeof(K) is ICloneable)
			{
				foreach( KeyValuePair<K, V> oEntry in oDicoSrc )
				{					
					oDicoDst.Add( (K)((ICloneable)oEntry.Key).Clone(), (V)((ICloneable)oEntry.Value).Clone() );
				}
			}

			return oDicoDst;
		}
	}

	static public class Message
	{
		// Affiche une Trace lors d'une Exception indiquant l'emplacement du déclencchement de l'exception.
		public static void Exception(Exception e)
		{			
			StackTrace st = new StackTrace();			
			string strPileAppel = StackTraceToString();			
			Trace.WriteLine( String.Format(
			@"!!!!! EXCEPTION !!!!!\nEXCEPTION :\n{0}\nCALL STACK :\n{1}\n!!!!!!!!!!!!!!!!!!!!!!!", e.ToString(), strPileAppel) );
		}

		static public string StackTraceToString()
		{
			StringBuilder sb = new StringBuilder(256);
			var frames = new System.Diagnostics.StackTrace().GetFrames();
			for (int i = 2; i < frames.Length; i++) /* 2 : Ignore current StackTraceToString method... and the second : Message.Exception*/
			{
				var currFrame = frames[i];
				var method = currFrame.GetMethod();
				sb.AppendLine(string.Format("{0}:{1}",                    
					method.ReflectedType != null ? method.ReflectedType.Name : string.Empty,
					method.Name));
			}
			return sb.ToString();
		}
	}

	
}
